/**
 * 用于生成uuid
 * @param{null}
 */

import dayjs from 'dayjs'
import _ from 'lodash'
import { getTaskId } from '@/api/common'
import { Message, MessageBox } from 'element-ui'
import QRCode from 'qrcodejs2'

export const S4 = () => {
  return (((1 + Math.random()) * 0x10000) | 0).toString(16).substring(1)
}
export const guid = () => {
  return (
    S4() +
    S4() +
    '-' +
    S4() +
    '-' +
    S4() +
    '-' +
    S4() +
    '-' +
    S4() +
    S4() +
    S4()
  )
}

/**
 * isEmptyObj 判断对象是否为空对象
 * @param {object} obj
 * @return boolean
 */
export const isEmptyObj = (obj) => JSON.stringify(obj) === '{}'

/**
 * rebuildObj 对象去掉空属性和前后空格
 * @param {object} obj
 * @return object
 */
export const rebuildObj = (obj = {}) => {
  const temp = obj
  for (const i in temp) {
    // 删除空属性
    if (
      temp[i] === '' ||
      temp[i] == null ||
      isEmptyObj(temp[i]) ||
      (Array.isArray(temp[i]) && !temp[i].length)
    ) {
      delete temp[i]
    }
    // 去除前后空格
    if (typeof temp[i] === 'string') {
      temp[i] = temp[i].replace(/(^\s*)|(\s*$)/g, '')
    }
  }
  return temp
}
/**
 * legitimacy 判断http请求参数里是否包含 & 字符
 * @param {object} obj
 * @return object
 */
export const legitimacy = (obj = {}) => {
  const temp = obj
  for (const i in temp) {
    if ((temp[i] + '').indexOf('&') !== -1) return false
  }
  return true
}

export const getRowIdentity = (row, rowKey) => {
  if (!row) throw new Error('row is required when get row identity')
  if (typeof rowKey === 'string') {
    if (rowKey.indexOf('.') < 0) {
      return row[rowKey]
    }
    const key = rowKey.split('.')
    let current = row
    for (let i = 0; i < key.length; i++) {
      current = current[key[i]]
    }
    return current
  } else if (typeof rowKey === 'function') {
    return rowKey.call(null, row)
  }
}
export const getValueByPath = (object, prop) => {
  prop = prop || ''
  const paths = prop.split('.')
  let current = object
  let result = null
  for (let i = 0, j = paths.length; i < j; i++) {
    const path = paths[i]
    if (!current) break

    if (i === j - 1) {
      result = current[path]
      break
    }
    current = current[path]
  }
  return result
}
export const getPropByPath = (obj, path, strict) => {
  let tempObj = obj
  path = path.replace(/\[(\w+)\]/g, '.$1')
  path = path.replace(/^\./, '')

  const keyArr = path.split('.')
  let i = 0
  for (let len = keyArr.length; i < len - 1; ++i) {
    if (!tempObj && !strict) break
    const key = keyArr[i]
    if (key in tempObj) {
      tempObj = tempObj[key]
    } else {
      if (strict) {
        throw new Error('please transfer a valid prop path to form item!')
      }
      break
    }
  }
  return {
    o: tempObj,
    k: keyArr[i],
    v: tempObj ? tempObj[keyArr[i]] : null,
  }
}
export const getButtons = (handlera, handlerb, handlerc) => {
  const commonBtns = [
    {
      label: '发布',
      type: 'success',
      click: handlera,
    },
    {
      label: '取消',
      type: 'danger',
      click: handlerb,
    },
    {
      label: '返回',
      type: 'info',
      click: handlerc,
    },
  ]
  return {
    add: [commonBtns[0], commonBtns[1]],
    edit: [commonBtns[0], commonBtns[1]],
    view: [commonBtns[2]],
  }
}

export const formatTime = (date = dayjs(), format = 'YYYY-MM-DD HH:mm:ss') => {
  const week = [
      '星期天',
      '星期一',
      '星期二',
      '星期三',
      '星期四',
      '星期五',
      '星期六',
    ],
    t = dayjs(date)
  const map = {
    y: t.year(),
    M: t.month(),
    d: t.date(),
    h: t.hour(),
    m: t.minute(),
    s: t.second(),
    S: t.millisecond(),
    w: t.day(),
  }
  if (format == 'day') {
    return week[map.w]
  } else {
    return t.format(format)
  }
}
export const getIndex = (currentPage, pageSize, index) => {
  return (currentPage - 1) * pageSize + index + 1
}

/**
 * plat 将多级json扁平化
 * @param {object} obj
 * @return object
 */
export const plat = (o, resobj) => {
  let keys = Object.keys(o)
  keys.forEach(function (item) {
    let v = o[item]
    let type = typeof v
    if (v && ['object', 'array'].indexOf(type) != -1) {
      plat(v, resobj)
    } else {
      resobj[item] = v
    }
  })
}

export const pageDownFile = (api = '', params = {}, type = 'location') => {
  let paramsUrl = ''
  getTaskId().then((res) => {
    _.forIn(_.merge(params, { taskId: res.data }), (val, key) => {
      paramsUrl = paramsUrl
        ? paramsUrl + '&' + key + '=' + val
        : paramsUrl + '?' + key + '=' + val
    })
    paramsUrl = process.env.VUE_APP_BASE_URL_API + api + paramsUrl
    if (type === 'open') {
      window.open(paramsUrl)
    } else {
      window.location.href = paramsUrl
    }
    messageBox.message({
      message: '数据已经导出，请注意查看',
    })
  })
}

export const formatQueryParams = (queryParams = {}) => {
  let params = {}
  _.forIn(queryParams, (val, key) => {
    if ((val !== null && val !== undefined) || val !== '') {
      params[key] = val
    }
  })

  return params
}

export const formatTableData = (data, columns) => {
  return _.map(data, (item) => {
    _.each(columns, (column) => {
      if (
        column.prop &&
        (item[column.prop] === '' ||
          item[column.prop] === null ||
          item[column.prop] === undefined)
      ) {
        item[column.prop] = '--'
      }
    })
    return item
  })
}

export const messageBox = {
  confirm: (text, title = '提示', options = {}) => {
    return MessageBox.confirm(
      text,
      title,
      _.merge({ confirmButtonText: '确定', cancelButtonText: '取消' }, options)
    )
  },
  alert: (text, title = '提示', options = {}) => {
    return MessageBox.alert(
      text,
      title,
      _.merge({ confirmButtonText: '确定' }, options)
    )
  },
  message: ({ type = 'alert', ...options } = {}) => {
    switch (type) {
      case 'add':
        return Message(
          _.merge(
            {
              showClose: true,
              type: 'success',
              message: '查询成功!',
            },
            options
          )
        )
      case 'delete':
        return Message(
          _.merge(
            {
              showClose: true,
              type: 'success',
              message: '删除成功!',
            },
            options
          )
        )
      case 'update':
        return Message(
          _.merge(
            {
              showClose: true,
              type: 'success',
              message: '修改成功!',
            },
            options
          )
        )
      case 'alert':
        return Message(
          _.merge(
            {
              showClose: true,
              type: 'success',
            },
            options
          )
        )
      default:
        break
    }
  },
}
export const getCurrentPage = (tableTata, currentPage) =>
  currentPage > 1 && tableTata.length === 1 ? currentPage - 1 : currentPage
export const isNumber = (obj) => {
  return typeof obj === 'number' && isFinite(obj)
}
export const isFunction = (obj) => {
  return typeof obj === 'function'
}
export const throttle = (fn, gapTime) => {
  if (!gapTime) {
    gapTime = 1000
  }
  let _lastTime = null
  return function () {
    let _nowTime = new Date()
    if (_nowTime - _lastTime > gapTime || !_lastTime) {
      fn.apply(this, arguments)
      _lastTime = _nowTime
    }
  }
}
export const debounce = (func, delay = 1000) => {
  let timer = null
  // 接受函数的所有参数
  return (...args) => {
    clearTimeout(timer)
    timer = setTimeout(() => {
      func(...args)
      timer = null
    }, delay)
  }
}

export const removeEmpty = (obj = {}) => {
  Object.keys(obj).forEach((key) => {
    ;(obj[key] && typeof obj[key] === 'object' && removeEmpty(obj[key])) ||
      ((obj[key] === '' || obj[key] === undefined || obj[key] === null) &&
        delete obj[key])
  })
  return obj
}
// 找到资源列表里有的数组
export const handleRouterFilter = (resourceIdArr, routes) => {
  return routes.filter((item) =>
    item.meta && item.meta.resourceId
      ? resourceIdArr.indexOf(item.meta.resourceId) > -1
      : true
  )
}

// 生成新的路由列表
export const handleRouter = (resourceIdArr, routes) => {
  return handleRouterFilter(resourceIdArr, routes).map((route) => ({
    ...route,
    children: route.children
      ? handleRouterFilter(resourceIdArr, route.children)
      : null,
  }))
}
export const handleRouterTreeCategory = (modules) => {
  const keyMap = {
    buttons: '按钮',
    dataColumns: '数据列',
    urls: '接口',
  }
  let arr = []
  Object.keys(modules).forEach((item) => {
    if (keyMap[item] && modules[item].length) {
      arr.push({
        label: keyMap[item],
        resourceId: 'label:' + item + ':' + modules.path,
        children: handleRouterTree(modules[item], item),
      })
    }
  })
  return arr
}
// 生成新树状结构
export const handleRouterTree = (permissionTreeArr, type) => {
  return permissionTreeArr.map(function (item) {
    let tmpItem = {
      label: item.showName || '',
      resourceId: type + ':' + item.path,
      disabled: item.updatable,
      contain: item.contain,
    }
    if (item.pages && item.pages.length) {
      tmpItem.children = handleRouterTree(item.pages, 'pages')
    }
    if (
      (item.buttons && item.buttons.length) ||
      (item.dataColumns && item.dataColumns.length) ||
      (item.urls && item.urls.length)
    ) {
      tmpItem.children = handleRouterTreeCategory(item)
    }
    return tmpItem
  })
}
export const handleCheckedKeys = (menuOptions, checkedKeys) => {
  menuOptions.forEach((item) => {
    if (item.children) {
      handleCheckedKeys(item.children, checkedKeys)
    } else {
      if (item.contain) {
        checkedKeys.push(item.resourceId)
      }
    }
  })
  return checkedKeys
}
export const genQrcode = (data) => {
  // let imgSize = 200
  // let padding = 30
  // let fontSize = 16
  let imgSize = 400
  let padding = 60
  let fontSize = 32
  let downloadFile = function (fileName, content) {
    let aLink = document.createElement('a')
    let evt = document.createEvent('HTMLEvents')
    evt.initEvent('click', true, true) //initEvent 不加后两个参数在FF下会报错  事件类型，是否冒泡，是否阻止浏览器的默认行为
    aLink.download = fileName
    aLink.href = content
    aLink.style = 'display: none'
    aLink.dispatchEvent(
      new MouseEvent('click', { bubbles: true, cancelable: true, view: window })
    ) //兼容火狐
  }
  _.each(data, function (o, index) {
    let item = o.socketId
    let qrcodeEl = document.createElement('div')
    qrcodeEl.id = 'qrcode' + index
    qrcodeEl.style.display = 'none'
    document.body.append(qrcodeEl)
    let qrcode = new QRCode('qrcode' + index, {
      text: process.env.VUE_APP_DOMAIN_NAME + '?deviceId=' + item,
      width: imgSize - padding * 2,
      height: imgSize - padding * 2,
      colorDark: '#000000',
      colorLight: '#ffffff',
      correctLevel: QRCode.CorrectLevel.H,
    })
    let img = new Image()
    img.src = document
      .getElementById('qrcode' + index)
      .getElementsByTagName('canvas')[0]
      .toDataURL('image/png')
    img.onload = function () {
      let canvas = document.createElement('canvas')
      canvas.width = imgSize
      canvas.height = imgSize
      let ctx = canvas.getContext('2d')
      ctx.fillStyle = '#fff'
      ctx.fillRect(0, 0, imgSize, imgSize)
      ctx.drawImage(
        img,
        padding,
        padding,
        imgSize - padding * 2,
        imgSize - padding * 2
      )
      ctx.fillStyle = '#000000'
      ctx.font = `${fontSize}px Arial`
      ctx.textAlign = 'center'
      ctx.fillText(
        'ID:' + item,
        imgSize / 2,
        imgSize - padding + fontSize + 2,
        imgSize
      )
      let data = canvas.toDataURL('image/png', 1)
      qrcode.clear()
      qrcodeEl.remove()
      setTimeout(() => {
        if (window.navigator.msSaveOrOpenBlob) {
          //是ie
          let bstr = atob(data.split(',')[1])
          let n = bstr.length
          let u8arr = new Uint8Array(n)
          while (n--) {
            u8arr[n] = bstr.charCodeAt(n)
          }
          let blob = new Blob([u8arr])
          window.navigator.msSaveOrOpenBlob(blob, item + '.' + 'png')
        } else {
          downloadFile(item + '.png', data)
        }
      }, 1000 * index)
    }
  })
}
export const isIE = () => {
  //ie
  if (!!window.ActiveXObject || 'ActiveXObject' in window) {
    return true
  } else {
    return false
  }
}
export const exportExcel = (data, fileName) => {
  let blob
  if (isIE()) {
    blob = new Blob([data], { type: 'application/vnd.ms-excel' })
    window.navigator.msSaveOrOpenBlob(blob, fileName + '.xlsx')
  } else {
    blob = new Blob([data], { type: 'application/vnd.ms-excel' })
    var objectUrl = URL.createObjectURL(blob)
    var a = document.createElement('a')
    document.body.appendChild(a)
    a.style = 'display: none'
    a.href = objectUrl
    a.download = fileName + '.xlsx' || 'excel表格.xlsx'
    a.click()
    document.body.removeChild(a)
  }
}
